package cn.cable.monitor.admin.trigger.http;

import cn.cable.monitor.admin.domain.model.entity.MonitorDataEntity;
import cn.cable.monitor.admin.domain.model.entity.MonitorDataMapEntity;
import cn.cable.monitor.admin.domain.model.entity.MonitorFlowDesignerEntity;
import cn.cable.monitor.admin.domain.model.valobj.MonitorTreeConfigVO;
import cn.cable.monitor.admin.domain.model.valobj.MonitorTreeConfigVO.Link;
import cn.cable.monitor.admin.domain.model.valobj.MonitorTreeConfigVO.Node;
import cn.cable.monitor.admin.domain.service.ILogAnalyticalService;
import cn.cable.monitor.admin.trigger.http.dto.MonitorDataDTO;
import cn.cable.monitor.admin.trigger.http.dto.MonitorDataMapDTO;
import cn.cable.monitor.admin.trigger.http.dto.MonitorFlowDataDTO;
import cn.cable.monitor.admin.trigger.http.dto.MonitorFlowDataDTO.LinkData;
import cn.cable.monitor.admin.trigger.http.dto.MonitorFlowDataDTO.NodeData;
import cn.cable.monitor.admin.types.Response;
import java.util.ArrayList;
import java.util.List;
import javax.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

/**
 * 监控控制器
 *
 * @author hsj
 * @date 2024/7/18 18:24
 */
@Slf4j
@RestController
@CrossOrigin("*")
@RequestMapping("/api/v1/monitor/")
public class MonitorController {

	@Resource
	private ILogAnalyticalService logAnalyticalService;

	@RequestMapping(value = "query_monitor_data_map_entity_list", method = RequestMethod.GET)
	public Response<List<MonitorDataMapDTO>> queryMonitorDataMapEntityList() {
		try {

			List<MonitorDataMapEntity> monitorDataMapEntities = logAnalyticalService.queryMonitorDataMapEntityList();
			List<MonitorDataMapDTO> monitorDataDTOS = new ArrayList<>(monitorDataMapEntities.size());
			for (MonitorDataMapEntity monitorDataMapEntity : monitorDataMapEntities) {
				monitorDataDTOS.add(MonitorDataMapDTO.builder().monitorId(monitorDataMapEntity.getMonitorId())
				                                     .monitorName(monitorDataMapEntity.getMonitorName()).build());
			}

			return Response.<List<MonitorDataMapDTO>>builder().code("0000").info("调用成功")
			               .data(monitorDataDTOS).build();

		} catch (Exception e) {
			log.error("查询监控列表数据失败", e);
			return Response.<List<MonitorDataMapDTO>>builder().code("0001").info("调用失败").build();
		}

	}

	@RequestMapping(value = "query_monitor_flow_map", method = RequestMethod.GET)
	public Response<MonitorFlowDataDTO> queryMonitorFlowMap(@RequestParam String monitorId) {
		try {
			log.info("查询监控流数据 monitorId:{}", monitorId);
			MonitorTreeConfigVO monitorTreeConfigVO = logAnalyticalService.queryMonitorFlowData(monitorId);
			List<Node> nodeList = monitorTreeConfigVO.getNodeList();
			List<Link> linkList = monitorTreeConfigVO.getLinkList();
			List<MonitorFlowDataDTO.NodeData> nodeDataList = new ArrayList<>();
			for (MonitorTreeConfigVO.Node node : nodeList) {
				nodeDataList.add(new MonitorFlowDataDTO.NodeData(
					node.getMonitorNodeId(),
					node.getMonitorNodeId(),
					node.getMonitorNodeName(),
					node.getMonitorNodeValue(),
					node.getLoc(),
					node.getColor()
				));
			}
			List<MonitorFlowDataDTO.LinkData> linkDataList = new ArrayList<>();
			for (MonitorTreeConfigVO.Link link : linkList) {
				String linkValue = link.getLinkValue();
				linkDataList.add("0".equals(linkValue) ?
				                 new MonitorFlowDataDTO.LinkData(link.getFromMonitorNodeId(), link.getToMonitorNodeId()) :
				                 new MonitorFlowDataDTO.LinkData(
					                 link.getFromMonitorNodeId(),
					                 link.getToMonitorNodeId(),
					                 link.getLinkKey(),
					                 linkValue
				                 ));
			}

			MonitorFlowDataDTO monitorFlowDataDTO = new MonitorFlowDataDTO();
			monitorFlowDataDTO.setNodeDataArray(nodeDataList);
			monitorFlowDataDTO.setLinkDataArray(linkDataList);

			// 返回结果
			return Response.<MonitorFlowDataDTO>builder()
			               .code("0000")
			               .info("调用成功")
			               .data(monitorFlowDataDTO).build();
		} catch (Exception e) {
			log.error("查询监控流数据失败 monitorId:{}", monitorId, e);
			return Response.<MonitorFlowDataDTO>builder().code("0001").info("调用失败").build();
		}
	}

	@RequestMapping(value = "query_monitor_data_list", method = RequestMethod.GET)
	public Response<List<MonitorDataEntity>> queryMonitorDataList(@RequestParam String monitorId,
		@RequestParam String monitorName, @RequestParam String monitorNodeId) {
		try {
			log.info("查询监控数据:{}", monitorId);
			List<MonitorDataEntity> monitorDataEntityList = logAnalyticalService.queryMonitorDataEntityList(MonitorDataEntity.builder()
			                                                                                                                 .monitorId(
				                                                                                                                 monitorId)
			                                                                                                                 .monitorName(
				                                                                                                                 monitorName)
			                                                                                                                 .monitorNodeId(
				                                                                                                                 monitorNodeId)
			                                                                                                                 .build());
			return Response.<List<MonitorDataEntity>>builder()
			               .code("0000")
			               .info("调用成功")
			               .data(monitorDataEntityList).build();
		} catch (Exception e) {
			log.error("查询监控流数据失败 monitorId:{}", monitorId, e);
			return Response.<List<MonitorDataEntity>>builder().code("0001").info("调用失败").build();
		}

	}

	@RequestMapping(value = "update_monitor_flower_design", method = RequestMethod.POST)
	public Response<Boolean> updateMonitorFlowDesigner(@RequestParam String monitorId, @RequestBody MonitorFlowDataDTO request) {

		try {

			log.info("更新監控图配置 monitorId :{}", monitorId);
			List<NodeData> nodeDataList = request.getNodeDataArray();
			List<LinkData> linkDataList = request.getLinkDataArray();
			List<MonitorFlowDesignerEntity.Node> nodeList = new ArrayList<>();
			for (MonitorFlowDataDTO.NodeData nodeData : nodeDataList) {
				nodeList.add(MonitorFlowDesignerEntity.Node.builder()
				                                           .monitorNodeId(nodeData.getKey())
				                                           .loc(nodeData.getLoc())
				                                           .build());
			}

			List<MonitorFlowDesignerEntity.Link> linkList = new ArrayList<>();
			for (MonitorFlowDataDTO.LinkData linkData : linkDataList) {
				linkList.add(MonitorFlowDesignerEntity.Link.builder()
				                                           .from(linkData.getFrom())
				                                           .to(linkData.getTo())
				                                           .build());
			}

			MonitorFlowDesignerEntity monitorFlowDesignerEntity = MonitorFlowDesignerEntity.builder()
			                                                                               .monitorId(monitorId)
			                                                                               .nodeList(nodeList)
			                                                                               .linkList(linkList)
			                                                                               .build();

			logAnalyticalService.updateMonitorFlowDesigner(monitorFlowDesignerEntity);

			return Response.<Boolean>builder().code("0000").info("调用成功").data(true).build();


		} catch (Exception e) {
			log.error("更新监控图配置失败 monitorId:{}", monitorId, e);
			return Response.<Boolean>builder().code("0001").info("调用失败").data(true).build();

		}


	}


}
